package com.jeesite.modules.warehouse.service;

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.*;

import com.jeesite.common.collect.ListUtils;
import com.jeesite.common.config.Global;
import com.jeesite.common.idgen.IdGen;
import com.jeesite.common.lang.DateUtils;
import com.jeesite.common.lang.ObjectUtils;
import com.jeesite.common.lang.StringUtils;
import com.jeesite.common.service.ServiceException;
import com.jeesite.common.utils.OrgUtil;
import com.jeesite.common.utils.excel.ExcelImport;
import com.jeesite.modules.common.vo.CommonSelectDataVO;
import com.jeesite.modules.sys.utils.UserUtils;
import com.jeesite.modules.warehouse.entity.excel.WarehouseImport;
import com.jeesite.modules.warehouse.enums.WarehouseCategoryEnum;
import com.jeesite.modules.warehouse.enums.WarehousePositionFlagEnum;
import com.jeesite.modules.warehouse.enums.WarehouseSourceTypeEnum;
import lombok.Synchronized;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.jeesite.common.entity.Page;
import com.jeesite.common.service.CrudService;
import com.jeesite.modules.warehouse.entity.Warehouse;
import com.jeesite.modules.warehouse.dao.WarehouseDao;
import org.springframework.web.multipart.MultipartFile;

import static com.jeesite.common.web.http.ServletUtils.renderResult;

/**
 * 仓库档案Service
 * @author 码脑洞
 * @version 2025-04-08
 */
@Service
public class WarehouseService extends CrudService<WarehouseDao, Warehouse> {
	
	/**
	 * 获取单条数据
	 * @param warehouse
	 * @return
	 */
	@Override
	public Warehouse get(Warehouse warehouse) {
		return super.get(warehouse);
	}
	
	/**
	 * 查询分页数据
	 * @param warehouse 查询条件
	 * @param warehouse page 分页对象
	 * @return
	 */
	@Override
	public Page<Warehouse> findPage(Warehouse warehouse) {
		return super.findPage(warehouse);
	}
	
	/**
	 * 查询列表数据
	 * @param warehouse
	 * @return
	 */
	@Override
	public List<Warehouse> findList(Warehouse warehouse) {
		return super.findList(warehouse);
	}
	
	/**
	 * 保存数据（插入或更新）
	 * @param warehouse
	 */
	@Override
	@Transactional
	public void save(Warehouse warehouse) {

		if (StringUtils.isBlank(warehouse.getCode())) {
			throw new ServiceException("仓库编码不能为空");
		}

		// 检查编码唯一性
		Warehouse entity = dao.getWarehouse(warehouse);
		if (entity != null){
			throw new ServiceException("仓库编码已存在，请重新输入");
		}

		super.save(warehouse);
	}
	
	/**
	 * 更新状态
	 * @param warehouse
	 */
	@Override
	@Transactional
	public void updateStatus(Warehouse warehouse) {
		super.updateStatus(warehouse);
	}
	
	/**
	 * 删除数据
	 * @param warehouse
	 */
	@Override
	@Transactional
	public void delete(Warehouse warehouse) {
		super.delete(warehouse);
	}

	public Boolean checkCodeUnique(String oldCode, String code) {
		if (StringUtils.isEmpty(code)) {
			return false;
		}
		Warehouse warehouse = new Warehouse();
		warehouse.setCode(code);
		if (code.equals(oldCode)) {
			return true;
		} else {
			return findWarehouseCodeOrName(warehouse) == null;
		}
	}

	public Warehouse findWarehouseCodeOrName(Warehouse warehouse) {
		return dao.findWarehouseCodeOrName(warehouse);
	}



	@Transactional
	public String importData(MultipartFile file) {
		// 1. 校验文件是否为空
		if (file == null || file.isEmpty()) {
			return "导入失败：文件为空，请上传有效文件！";
		}

		// 2. 校验文件格式（假设支持 CSV 和 Excel）
		String fileName = file.getOriginalFilename();
		if (fileName == null || !(fileName.endsWith(".csv") || fileName.endsWith(".xlsx"))) {
			return "导入失败：仅支持 CSV 或 Excel 文件格式！";
		}


		// 读取Excel文件中的数据
		List<WarehouseImport> importList;
		try {
			importList = new ExcelImport(file, 2, 0).getDataList(WarehouseImport.class);
		} catch (Exception e) {
			throw new RuntimeException(e);
		}


		// 检查 importList 中是否存在重复编码
		List<String> errorMessages = new ArrayList<>();
		Set<String> codeSet = new HashSet<>();
		for (WarehouseImport warehouseImport : importList) {
			if (codeSet.contains(warehouseImport.getCode())) {
				return "导入失败：仓库编码 [" + warehouseImport.getCode() + "] 在文件中重复，请检查文件内容！";
			}
			codeSet.add(warehouseImport.getCode());
		}

		for (int i = 0; i < importList.size(); i++) {
			WarehouseImport importData = importList.get(i);
			int rowNum = i + 3; // Excel行号从1开始，前两行是标题和表头

			if (StringUtils.isBlank(importData.getCode())) {
				errorMessages.add("第" + rowNum + "行：仓库编码不能为空");
			}
			if (StringUtils.isBlank(importData.getName())) {
				errorMessages.add("第" + rowNum + "行：仓库名称不能为空");
			}
			if (StringUtils.isBlank(importData.getCategory())) {
				errorMessages.add("第" + rowNum + "行：仓库分类不能为空");
			}
			if (StringUtils.isBlank(importData.getPositionFlag())) {
				errorMessages.add("第" + rowNum + "行：启用库位不能为空");
			}

			if (StringUtils.isNotBlank(importData.getCode())) {
				codeSet.add(importData.getCode());
			}
		}

		// 如果存在校验错误，一次性抛出
		if (!errorMessages.isEmpty()) {
			return renderResult(Global.FALSE, StringUtils.join(errorMessages, "; "));
		}

		// 校验编码唯一性，是否存在库中
		List<Warehouse> list = dao.findWarehouseList(new ArrayList<>(codeSet));
		if (!list.isEmpty()) {
			return renderResult(Global.FALSE, "导入失败：导入的数据存在仓库编码已在数据库中");
		}

		Date currentDate = new Date();
		List<Warehouse> validWarehouses = new ArrayList<>();
		for (WarehouseImport warehouseImport : importList) {
			Warehouse warehouse = new Warehouse();
			warehouse.setAutoId(IdGen.autoId());
			warehouse.setOrgId(OrgUtil.getOrgId());
			warehouse.setOrgCode(OrgUtil.getOrgCode());
			warehouse.setOrgName(OrgUtil.getOrgName());
			warehouse.setCode(warehouseImport.getCode());
			warehouse.setName(warehouseImport.getName());
			warehouse.setCategory(WarehouseCategoryEnum.getCode(warehouseImport.getCategory()));
			warehouse.setPositionFlag(WarehousePositionFlagEnum.getCode(warehouseImport.getPositionFlag()));
			warehouse.setStatus(Warehouse.STATUS_NORMAL);
			warehouse.setSourceType("1");
			warehouse.setCreateBy(UserUtils.getUser().getCreateBy());
			warehouse.setCreateDate(currentDate);
			warehouse.setUpdateBy(UserUtils.getUser().getCreateBy());
			warehouse.setUpdateDate(currentDate);
			validWarehouses.add(warehouse);
		}

		// 5. 批量保存有效数据
		if (!validWarehouses.isEmpty()) {
			try {
				ListUtils.pageList(validWarehouses, 100, objs -> dao.insertBatch((List<Warehouse>) objs[0]));
			} catch (Exception e) {
				return "导入失败：数据保存异常，请稍后重试！";
			}
		}
		return renderResult(Global.TRUE, "导入成功：共导入 " + validWarehouses.size() + " 条数据！");
	}

	/**
	 * 获取仓库下拉框数据
	 * @return
	 */
	public List<CommonSelectDataVO> selectWarehouseList() {
		return dao.selectWarehouseList();
	}
}